
#include "APP.hpp"
#ifdef DBG_TAG
#undef DBG_TAG
#endif
#ifdef DBG_LVL
#undef DBG_LVL
#endif

#define DBG_TAG "app"
#define DBG_LVL DBG_LOG

extern "C"
{
#include <rtdbg.h>
#include "stm32f1xx.h"
#include "drv_common.h"
#include "stm32f1xx.h"
}

float power_v= 6;
uint32_t sleep_time = 0;
button_fun bt_fun = button_fun_none;

double transfer_adc_value_to_need_V(uint32_t adc_value)
{
    double pin_V; //adc管脚电压
    double battery_V; //adc管脚电压

    pin_V = adc_value * 3.3 / 4096; //adc管脚电压换算
    battery_V = pin_V *2.2/1.2 ;
    return battery_V;
}

CHIP_ADC battry_adc("adc1", 10, 50, FA_Filter_Type_MV, transfer_adc_value_to_need_V);
CHIP_PWM servor_pwm("pwm3", 1, chip_pwm_drive_type_HIGH, 50, 50);
CHIP_OUTPUT_PIN servor_pin(GET_PIN(C,7), chip_output_pin_out_mode_normal, chip_pin_level_LOW);

CHIP_OUTPUT_PIN low_power_pin(GET_PIN(D,1), chip_output_pin_out_mode_normal, chip_pin_level_HIGH);

int servor_open()
{
    servor_pin.CHIP_OUTPUT_PIN_write(chip_pin_level_HIGH);
    servor_pwm.CHIP_PWM_open();
    servor_pwm.CHIP_PWM_change_duty_ratio(2.5);
    rt_thread_mdelay(3000);
    servor_pwm.CHIP_PWM_change_duty_ratio(12.5);
    rt_thread_mdelay(500);
    servor_pwm.CHIP_PWM_close();
    servor_pin.CHIP_OUTPUT_PIN_write(chip_pin_level_LOW);
    return 0;
}


void battry_thread_entry(void *pra)
{
    while (1)
    {
        power_v = battry_adc.CHIP_ADC_measure();
        LOG_D("battery %f v", power_v);
        if(power_v < 4)//小于4V低电量告警
        {
            low_power_pin.CHIP_OUTPUT_PIN_write(chip_pin_level_LOW);
        }
        rt_thread_mdelay(1000);
    }
}

void go_adc()
{
    rt_thread_t tid = rt_thread_create("bat", battry_thread_entry, NULL, 2048, 10, 20);
    if (tid) rt_thread_startup(tid);

}
MSH_CMD_EXPORT(go_adc, go_adc)

CHIP_INPUT_PIN bt1_pin(GET_PIN(A,1), chip_input_pin_mode_simple, chip_input_pin_pull_mode_none,NULL,NULL);
CHIP_INPUT_PIN bt2_pin(GET_PIN(A,2), chip_input_pin_mode_simple, chip_input_pin_pull_mode_none,NULL,NULL);
BUTTON_SIMPLE func_bt(&bt2_pin, button_press_signal_mode_LOW_active);
BUTTON_SIMPLE choice_bt(&bt1_pin,button_press_signal_mode_LOW_active);

CHIP_OUTPUT_PIN work_pin(GET_PIN(D,0), chip_output_pin_out_mode_normal, chip_pin_level_HIGH);
CHIP_OUTPUT_PIN mode_pin(GET_PIN(C,14), chip_output_pin_out_mode_normal, chip_pin_level_HIGH);
CHIP_OUTPUT_PIN fun_pin(GET_PIN(C,15), chip_output_pin_out_mode_normal, chip_pin_level_HIGH);

void func_bt_scan_thread_entry(void *p)
{
    while(1)
    {
        func_bt.BUTTON_SIMPLE_update_in_thread();
        rt_thread_mdelay(100);
    }

}

void choice_bt_scan_thread_entry(void *p)
{
    while(1)
    {
        choice_bt.BUTTON_SIMPLE_update_in_thread();
        rt_thread_mdelay(100);
    }

}

void func_bt_thread_entry(void *p)
{
    button_press_signal flag;
    while(1)
    {
        flag = func_bt.BUTTON_SIMPLE_read_button_press_status();
        switch(flag)
        {
        case button_press_signal_pressed:
            bt_fun = button_fun_add_fp;
            break;
        case button_press_signal_long_pressed:
            bt_fun = button_fun_delete_fp;
            break;
        default:
            break;
        }
        rt_thread_mdelay(100);
    }

}

void choice_bt_thread_entry(void *p)
{
    button_press_signal flag;
    while(1)
    {
        flag = choice_bt.BUTTON_SIMPLE_read_button_press_status();
        switch(flag)
        {
        case button_press_signal_pressed:
            switch(bt_fun)
            {
            case button_fun_add_fp:
                fp_add();
                bt_fun = button_fun_none;
                break;
            case button_fun_delete_fp:
                fp_delete();
                bt_fun = button_fun_none;
                break;
            default:
                break;
            }
            break;
        case button_press_signal_long_pressed:
            bt_fun = button_fun_none;
            break;
        default:
            break;
        }
        rt_thread_mdelay(100);
    }
}


void led_thread_entry(void *p)
{
    work_pin.CHIP_OUTPUT_PIN_write(chip_pin_level_LOW);

    while(1)
    {
        switch(bt_fun)
        {
        case button_fun_add_fp:
            mode_pin.CHIP_OUTPUT_PIN_write(chip_pin_level_LOW);
            fun_pin.CHIP_OUTPUT_PIN_write(chip_pin_level_HIGH);
            break;
        case button_fun_delete_fp:
            mode_pin.CHIP_OUTPUT_PIN_write(chip_pin_level_HIGH);
            fun_pin.CHIP_OUTPUT_PIN_write(chip_pin_level_LOW);
            break;
        default:
            mode_pin.CHIP_OUTPUT_PIN_write(chip_pin_level_HIGH);
            fun_pin.CHIP_OUTPUT_PIN_write(chip_pin_level_HIGH);
            break;
        }
        rt_thread_mdelay(100);
    }
}

void go_bt()
{
    rt_thread_t tid;
    tid = rt_thread_create("bt_fun_s", func_bt_scan_thread_entry, NULL, 2048, 9, 20);
    if (tid) rt_thread_startup(tid);
    tid = rt_thread_create("bt_choice_s", choice_bt_scan_thread_entry, NULL, 2048, 9, 20);
    if (tid) rt_thread_startup(tid);
    tid = rt_thread_create("bt_fun", func_bt_thread_entry, NULL, 2048, 9, 20);
    if (tid) rt_thread_startup(tid);
    tid = rt_thread_create("bt_choice", choice_bt_thread_entry, NULL, 2048, 9, 20);
    if (tid) rt_thread_startup(tid);
    tid = rt_thread_create("led", led_thread_entry, NULL, 1024, 20, 20);
    if (tid) rt_thread_startup(tid);

}
MSH_CMD_EXPORT(go_bt, go_bt)

struct serial_configure serial_config =
{
 BAUD_RATE_57600,
 DATA_BITS_8,
 STOP_BITS_1,
 PARITY_NONE,
 BIT_ORDER_LSB,
 NRZ_NORMAL,
  256,
  RT_SERIAL_FLOWCONTROL_NONE,
 0
};

CHIP_INPUT_PIN touch_pin(GET_PIN(A,0), chip_input_pin_mode_simple, chip_input_pin_pull_mode_down,NULL,NULL);
CHIP_UART fp_uart("uart3",&serial_config);
CHIP_OUTPUT_PIN fp_power_pin(GET_PIN(B,2), chip_output_pin_out_mode_normal, chip_pin_level_LOW);
HLC_FP fp(&fp_uart,&fp_power_pin,&touch_pin,hlc_fp_device_type_FPM383,0x0);

/* 接收数据回调函数 */
rt_err_t uart_input_callback(rt_device_t dev, rt_size_t size)
{
    /* 串口接收到数据后产生中断，调用此回调函数，然后发送接收信号量 */
//    LOG_D("in");
    fp_uart.CHIP_UART_rx_default_callback();
    return RT_EOK;
}

void uart_rx_thread_entry(void *p)
{
    fp_uart.CHIP_UART_rx_default_thread_handler();
}


void fp_thread_entry(void *p)
{
    fp.HLC_FP_take_mutex();
    fp.HLC_FP_reset();
    fp.HLC_FP_release_mutex();

    while(1)
    {
        fp.HLC_FP_take_mutex();
        if(fp.HLC_FP_check_fp_on_pos() == hlc_fp_status_ok)
        {
            sleep_time = 0;
            if(fp.HLC_FP_match_fp()== hlc_fp_status_ok)
            {
                //指纹成功
                servor_open();
            }
        }
        if(power_v < 4)
        {
            fp.HLC_FP_led_control(0x01,0x05,0x22,0x22,0x00);
            rt_thread_mdelay(500);
        }
        fp.HLC_FP_release_mutex();
        rt_thread_mdelay(100);
    }

}

int fp_add()
{
    fp.HLC_FP_take_mutex();
    fp.HLC_FP_reset();
    fp.HLC_FP_auto_reg_fp();
    fp.HLC_FP_reset();
    fp.HLC_FP_release_mutex();
    return 0;
}

int fp_delete()
{
    fp.HLC_FP_take_mutex();
    fp.HLC_FP_reset();
    fp.HLC_FP_delete_all_fp();
    fp.HLC_FP_reset();
    fp.HLC_FP_release_mutex();
    return 0;
}

int fp_clean_touch_and_sleep()
{
    fp.HLC_FP_take_mutex();
    fp.HLC_FP_reset();
    while(touch_pin.CHIP_INPUT_PIN_read() != chip_pin_level_LOW)
    {
        fp.HLC_FP_sleep();
        rt_thread_mdelay(100);
        LOG_D("waiting for touch pin down");
    }
    fp.HLC_FP_release_mutex();
    return 0;
}

void go_fp()
{
    rt_thread_t tid;

    fp_uart.CHIP_UART_init_rx_interrupt(uart_input_callback);
    tid = rt_thread_create("uart3_rx", uart_rx_thread_entry, RT_NULL, 2048, 10, 10);
    if (tid != RT_NULL) rt_thread_startup(tid);

    tid = rt_thread_create("fp", fp_thread_entry, RT_NULL, 2048, 11, 10);
    if (tid != RT_NULL) rt_thread_startup(tid);
}
MSH_CMD_EXPORT(go_fp, go_fp)

void sleep_thread_entry(void *p)
{
    while(1)
    {
        if(bt_fun == button_fun_none)
            sleep_time += 1000;
        else
            sleep_time = 0;

        if(sleep_time >= 10000)
            break;
        rt_thread_mdelay(1000);
    }
    fp_clean_touch_and_sleep();
    //使能电源时钟
    __HAL_RCC_PWR_CLK_ENABLE();
    //使能唤醒引脚
    HAL_PWR_EnableWakeUpPin(PWR_WAKEUP_PIN1);
    //清除唤醒标记
    __HAL_PWR_CLEAR_FLAG(PWR_FLAG_WU);
    //睡眠
    HAL_PWR_EnterSTANDBYMode();

}

void go_sleep()
{
    rt_thread_t tid;
    tid = rt_thread_create("sleep", sleep_thread_entry, RT_NULL, 2048, 5, 100);
    if (tid != RT_NULL) rt_thread_startup(tid);
}
MSH_CMD_EXPORT(go_sleep, go_sleep)

int init()
{
    //晶振管脚复用
    __HAL_AFIO_REMAP_PD01_ENABLE();

    go_adc();
    go_bt();
    go_fp();
    go_sleep();
    return 0;
}
//MSH_CMD_EXPORT(init,init)
INIT_APP_EXPORT(init);

